package com.lvhx.springboot.partitioner;


import com.lvhx.springboot.entity.batch.BatchParameter;
import com.lvhx.springboot.entity.batch.BatchParameterConfig;
import com.lvhx.springboot.entity.batch.BatchParameterConfigExample;
import com.lvhx.springboot.mapper.batch.BatchParameterConfigMapper;
import com.lvhx.springboot.mapper.batch.BatchParameterMapper;
import com.lvhx.springboot.springbatch.base.Parameters;
import com.lvhx.springboot.utils.DateUtil;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.annotation.Scope;
import org.springframework.stereotype.Component;

import javax.annotation.Resource;
import java.util.Calendar;
import java.util.Date;
import java.util.List;
import java.util.Map;

@Component("parametersProvider")
@Scope("job")
public class CoreParametersProvider implements ParametersProvider {
    public static final String TODAY = "TODAY";
    @Autowired
    private BatchParameterMapper batchParameterMapper;
    @Autowired
    private BatchParameterConfigMapper batchParameterConfigMapper;
    @Value("#{jobParameters[PostDate]}")
    private Date postDate;
//    @Resource(name = "batchCodeMap")
//    private Map<String, String> batchCodeMap;

    @Override
    public Parameters loadParameters(String configKey) {
        Parameters paraMap = parseConfig(getConfig(configKey));
//    	generateGlSeqNo(configKey, paraMap);
        return paraMap;
    }

    /**
     * 根据配置好的batchCode生成glSeqNo,如果没有配置则不进行生成
     */
//	private void generateGlSeqNo(String configKey, Parameters paraMap) {
//		if (batchCodeMap.get(configKey) != null) {
//			String glSeqNo = null;
//			String batchCode = batchCodeMap.get(configKey);
//			if (paraMap.getDate("EFF") != null) {
//				glSeqNo = BatchIdGenerator.generateWandaBatchId(paraMap.getDate("EFF"), batchCode);
//			} else {
//				glSeqNo = BatchIdGenerator.generateWandaBatchId(postDate, batchCode);
//			}
//			paraMap.putString(DataMapKey.BATCH_GL_SEQ_NO, glSeqNo);
//		}
//	}
    private Parameters parseConfig(List<BatchParameterConfig> list) {
        Parameters paraMap = new Parameters();
        if (list != null && !list.isEmpty()) {
            for (BatchParameterConfig item : list) {
                BatchParameter p = batchParameterMapper.selectByPrimaryKey(item.getParametercd());
                if ("NUM".equals(p.getDatatypcd())) {
                    paraMap.putLong(item.getParametercd(), Long.parseLong(item.getParametervalue()));
                } else if ("DATE".equals(p.getDatatypcd())) {
                    paraMap.putDate(item.getParametercd(), parseEffDate(item.getParametervalue(), postDate));
                } else {
                    paraMap.putString(item.getParametercd(), item.getParametervalue());
                }
            }
        }
        // TODO 考虑是否需要设置这些默认字段
//        paraMap.putData("BKID", BankWidget.getDefaultBankId());
//        paraMap.putData("BRCH", BankWidget.getDefaultBranchNbr());
        // 从上下文中获取柜员号
//        try {
//			EventContext eventCtx = EventContextUtil.getEventContextFromTracer();
//			paraMap.putData("TELL", eventCtx.getOperator());
//			paraMap.putData(DataMapKey.SOURCE_ID, eventCtx.getChannelId());
//		} catch (TracerException e) {
//			e.printStackTrace();
//		}
        return paraMap;
    }

    /**
     * 从字符串中解析生效日期
     *
     * @param parameterValue 字符串参数值
     * @param postDate       记账日期
     * @return
     */
    private Date parseEffDate(String parameterValue, Date postDate) {
        if (null != parameterValue && parameterValue.contains(TODAY)) {
            if (!parameterValue.endsWith(TODAY)) {
                int days = parseOffsetDays(parameterValue);
                return addDays(postDate, days);
            }
            return postDate;
        } else {
            return DateUtil.dateFormatToDate(parameterValue);
        }
    }

    /**
     * 解析相对于记账日期的偏移天数
     *
     * @param parameterValue 字符串参数值
     * @return 相对于记账日期的偏移天数
     */
    private int parseOffsetDays(String parameterValue) {
        return Integer.parseInt(parameterValue.substring(TODAY.length()));
    }

    private List<BatchParameterConfig> getConfig(String configKey) {
        if (configKey == null || configKey.isEmpty()) {
            return null;
        }
        BatchParameterConfigExample exam = new BatchParameterConfigExample();
        exam.createCriteria().andConfigkeyEqualTo(configKey);
        return batchParameterConfigMapper.selectByExample(exam);
    }

    private static Date addDays(Date date, long nbrOfDays) {
        if (date == null)
            throw new IllegalArgumentException("date cannot be null");

        Calendar c = Calendar.getInstance();
        c.setTime(date);

        c.add(Calendar.DAY_OF_YEAR, (int) nbrOfDays);
        return c.getTime();
    }
}
